#ifndef BORDERSTRATEGY_H
#define BORDERSTRATEGY_H

#pragma once

#include "../../ToolkitLayer.h"
#include <LDF/VisComponentStrategy.h>

class LargeDisplayEvent;


/**
 * This strategy defines a rectangular border around a component using its
 * values for width and height. The color and line width of the border can be
 * specified by the user, as well as if any of them should or shouldn't be
 * drawn.
 *
 * @author Fabricio Anastacio - fabriciocfa@yahoo.com
 * @since August 2, 2007
 */
class TOOLKITLAYER_API BorderStrategy : public VisComponentStrategy
{
	// Attributes
protected:
	/** The color of the border. */
	float color[4];
	/** The color of the border of the selected component. */
	float colorSelected[4];
	/** The line width of the border. */
	float borderWidth;
	/** The line width of the boder of a selected component. */
	float selectedBorderWidth;
	/** If true the border is drawn. */
	bool drawBorder;
	/** If true the selected border is drawn. */
	bool drawSelectedBorder;

	/** The display list identifier. */
	unsigned int dlBorder;
	/** The width value currently used by the display list. */
	unsigned int dlWidth;
	/** The height value currently used by the display list. */
	unsigned int dlHeight;
	

	// Methods
public:
	/**
	 * Constructs a border strategy.
	 */
	BorderStrategy(void);
	/**
	 * Destroys a border strategy.
	 */
	~BorderStrategy(void);


	// ACCESSOR METHODS
	/**
	 * Returns the color used to draw the border (using an array of 4 floats).
	 *
	 * @return the color used to draw the border.
	 */
	inline float* getColor() { return color; };
	/**
	 * Sets the color to be used for drawing the border (using an array of 4
	 * floats).
	 *
	 * @param c the color to be used for drawing the border.
	 */
	inline void setColor(float* c) {
		color[0] = c[0]; color[1] = c[1]; color[2] = c[2]; color[3] = c[3]; createDisplayList();
	};
	/**
	 * Returns the color used to draw the selected border (using an array of 4
	 * floats).
	 *
	 * @return the color used to draw the selected border.
	 */
	inline float* getSelectedColor() { return colorSelected; };
	/**
	 * Sets the color to be used for drawing the selected border (using an
	 * array of 4 floats).
	 *
	 * @param c the color to be used for drawing the selected border.
	 */
	inline void setSelectedColor(float* c) {
		colorSelected[0] = c[0]; colorSelected[1] = c[1]; colorSelected[2] = c[2];
		colorSelected[3] = c[3]; createDisplayList();
	};
	/**
	 * Returns the value of the border line width.
	 *
	 * @return the value of the border line width.
	 */
	inline float getBorderWidth() { return borderWidth; };
	/**
	 * Sets the value of the border line width.
	 *
	 * @param f the value to be used as the border line width.
	 */
	inline void setBorderWidth(float w) { borderWidth = w; createDisplayList(); };
	/**
	 * Returns the value of the selected border line width.
	 *
	 * @return the value of the selected border line width.
	 */
	inline float getSelectedBorderWidth() { return selectedBorderWidth; };
	/**
	 * Sets the value of the selected border line width.
	 *
	 * @param f the value to be used as the selected border line width.
	 */
	inline void setSelectedBorderWidth(float w) { selectedBorderWidth = w; createDisplayList(); };
	/**
	 * Returns true if the border should be drawn.
	 *
	 * @return true if the border should be drawn, false otherwise.
	 */
	inline bool getDrawBorder() { return drawBorder; };
	/**
	 * Sets if the border should be drawn.
	 *
	 * @param value true if the border should be drawn, false otherwise.
	 */
	inline void setDrawBorder(bool value) { drawBorder = value; };
	/**
	 * Returns true if the selected border should be drawn.
	 *
	 * @return true if the selected border should be drawn, false otherwise.
	 */
	inline bool getDrawSelectedBorder() { return drawSelectedBorder; };
	/**
	 * Sets if the selected border should be drawn.
	 *
	 * @param value true if the selected border should be drawn, false otherwise.
	 */
	inline void setDrawSelectedBorder(bool value) { drawSelectedBorder = value; };


protected:
	/**
	 * Creates the display list to draw this border.
	 */
	virtual void createDisplayList();

	/**
	 * Defines the drawing strategy for the associated component.
	 *
	 * @param enablePicking if true, draw for selection mode (adding the
	 * component id).
	 */
	virtual void draw(const std::vector<unsigned long>& selectedIds);
	
};

#endif // BORDERSTRATEGY_H
